#include "PreCompiled.h"
#include "Application_App.h"
#include "BitmapFactoryInst.h"

#include "Icons/images.cpp"
#include "Icons/Feature.xpm"
#include "Icons/Document.xpm"
#include "Icons/BmpFactoryIcons.cpp"

#include <QtSvg/QSvgRenderer>

class BitmapFactoryInstP
{
public:
	QMap<std::string,const char**>xpmMap;
	QMap<std::string,QPixmap>xpmCache;
	QStringList paths;
};
BitmapFactoryInst* BitmapFactoryInst::_pcSingleton = 0;


BitmapFactoryInst::BitmapFactoryInst(void)
{
	d = new BitmapFactoryInstP;

}

BitmapFactoryInst::~BitmapFactoryInst(void)
{
	delete d;
}
void BitmapFactoryInst::addPath(const QString& path)
{
  d->paths.push_back(path);
}
BitmapFactoryInst& BitmapFactoryInst::instance()
{
	if (!_pcSingleton)
	{
		_pcSingleton = new BitmapFactoryInst;

		_pcSingleton->addPath(QString::fromAscii("%1/furniture/icons").arg(QString::fromUtf8(GetApplication().GetHomePath())));
		_pcSingleton->addPath(QLatin1String(":/icons/"));
		_pcSingleton->addPath(QLatin1String(":/Icons/"));
	}
	return *_pcSingleton;
}
void BitmapFactoryInst::addXPM(const char* name,const char** pXPM)
{
	d->xpmMap[name] = pXPM;
}

QPixmap BitmapFactoryInst::pixmap(const char* name)const
{
	if (!name || *name == '\0')
		return QPixmap(px);

	// as very first test check whether the pixmap is in the cache
	QMap<std::string, QPixmap>::ConstIterator it = d->xpmCache.find(name);
	if (it != d->xpmCache.end())
		return it.value();

	// now try to find it in the built-in XPM
	QPixmap icon;
	QMap<std::string,const char**>::ConstIterator It = d->xpmMap.find(name);
	if (It != d->xpmMap.end())
		icon = QPixmap(It.value());

	// Try whether an absolute path is given
	QString fn = QString::fromUtf8(name);
	if (icon.isNull())
		loadPixmap(fn, icon);

	// try to find it in the given directories
	if (icon.isNull()) {
		bool found = false;
		QList<QByteArray> formats = QImageReader::supportedImageFormats();
		formats.prepend("SVG"); // check first for SVG to use special import mechanism
		for (QStringList::ConstIterator pt = d->paths.begin(); pt != d->paths.end() && !found; ++pt) {
			QDir d(*pt);
			QString fileName = d.filePath(fn);
			if (loadPixmap(fileName, icon)) {
				found = true;
				break;
			}
			else {
				// Go through supported file formats
				for (QList<QByteArray>::iterator fm = formats.begin(); fm != formats.end(); ++fm) {
					QString path = QString::fromAscii("%1.%2").arg(fileName).
						arg(QString::fromAscii((*fm).toLower().constData()));
					if (loadPixmap(path, icon)) {
						found = true;
						break;
					}
				}
			}
		}
	}

	if (!icon.isNull()) {
		d->xpmCache[name] = icon;
		return icon;
	}

	return QPixmap(px);
	   
}

bool BitmapFactoryInst::loadPixmap(const QString& filename,QPixmap& icon)const
{
	QFileInfo fi(filename);
	if (fi.exists()) {
		// first check if it's an SVG because Qt's qsvg4 module shouldn't be used therefore
		if (fi.suffix().toLower() == QLatin1String("svg")) {
			QFile svgFile(filename);
			if (svgFile.open(QFile::ReadOnly | QFile::Text)) {
				QByteArray content = svgFile.readAll();
				icon = pixmapFromSvg(content, QSize(64,64));
			}
		}
		else {
			// try with Qt plugins
			icon.load(filename);
		}
	}

	return !icon.isNull();;
}
QPixmap BitmapFactoryInst::pixmapFromSvg(const QByteArray& contents,const QSize& size)const
{

	QImage image(size, QImage::Format_ARGB32_Premultiplied);

 	image.fill(0x00000000);
 
 	QPainter p(&image);
 
 	QSvgRenderer svg(contents);
 
 	svg.render(&p);
 
 	p.end();

	return QPixmap::fromImage(image);
}


